// Synapse.cpp : Defines the entry point for the console application.
//

#ifndef _WIN32_WINNT            
#define _WIN32_WINNT 0x0500     // Change this to the appropriate value to target other versions of Windows.
#endif

#include <stdio.h>
#include <tchar.h>
#include "synchrony.h"

// to demonstrate the sharing of objects (in C++ only), we wrap a float into a struct here
struct Float
{
	Float() : value(0) {}
	Float(float _val) : value(_val) {}
	float value;
};

// to demonstrate extended Synchrony headers (this one adds duration)
struct SynchroSampleInfoExt : public SynchroSampleInfo
{
	SynchroSampleInfoExt() : duration(0) {}

	//! Duration time of the sample.
	long long duration;
};

int _tmain(int /*argc*/, _TCHAR* /*argv[]*/)
{
	// Example 1: A Synapse storing an array of floats
	Synapse<float> myFloats;
	myFloats.Create("Shared_Floats_Name", 10); // create float array, size 10
	myFloats.Write(9); // write the value 9 into the first array element
	myFloats.Write(3.5f, 4); // write the value 3.5 into the 5th array element
    
	Synapse<float> yourFloats;
	yourFloats.Open("Shared_Floats_Name"); // open above float array
	float localArray[5];
	yourFloats.ReadArray(localArray, 4); // read first four elements of shared float array into local array
	localArray[4] = yourFloats.ReadCopy(4); // read 5th element of shared array into local array
	for (int i = 0; i < 5; i++) { printf("%f ", localArray[i]); }
	printf("\n");

	/* 
	// Objects example
	Synapse<Float> myFloats;
	myFloats.Create("Shared_Floats_Name", 10); // create float array, size 10
	myFloats.Write(9); // write the value 9 into the first array element
	myFloats.Write(3.5f, 4); // write the value 3.5 into the 5th array element
    
	Synapse<Float> yourFloats;
	yourFloats.Open("Shared_Floats_Name"); // open above float array
	Float localArray[5];
	yourFloats.ReadArray(localArray, 4); // read first four elements of shared float array into local array
	localArray[4] = yourFloats.ReadCopy(4); // read 5th element of shared array into local array
	for (int i = 0; i < 5; i++) { printf("%f ", localArray[i].value); }
	printf("\n");
	*/
		
	myFloats.Release(); // should close Synapse once done with it (but not required)
	yourFloats.Release();
		
	// Example 2: A Synapse storing a string
	Synapse<char> myString;
	myString.Create("Shared_String_Name", 20);
	myString.WriteArray("I am legend.");
		
	Synapse<char> yourString;
	yourString.Open("Shared_String_Name");
	char localString[20];
	yourString.ReadArray(localString);
	printf("%s\n", localString);
		
	myString.Release();
	yourString.Release();

	// Example 3: Send a message to Head X (if running).
	if (Synapse<long>::Exists("Head-X"))
	{
		Synapse<long> myHeadVersion;
		myHeadVersion.Open("Head-X(1)");
		printf("Head X detected: version %d\n", myHeadVersion.ReadCopy());

		Synapse<long> myHeadStatus;
		myHeadStatus.Open("Head-X(1)-Status");
		myHeadStatus.SetAsRead(); // so that IsNew() will work below

		Synapse<char> myHeadCommand;
		myHeadCommand.Open("Head-X(1)-Command");
		myHeadCommand.ProtectWriteArray("Hello user. I am connected through C++ Synapse.");
		printf("-Pause-");
						myHeadCommand.ProtectWriteArray("Kabul is lovely this time of year.");
		printf("Speaking");
		myHeadStatus.WaitForNew(); // wait for the head to start speaking
		while (myHeadStatus.ReadCopy(1) > 0)
		{
			printf(".");
			Sleep(250);
		}
		printf("\nDone speaking.\n");
	}
	else
	{
		printf("No Head X instance detected.\n");
	}

	// Example 4: A Synchrony ring buffer.
    Synchrony<int, SynchroSampleInfoExt> myBuffer; // you can omit the SynchroSampleInfoExt if you just want to use normal sample headers
    myBuffer.SetBufferSize(1000);
    myBuffer.Create("Synchrony_Buffer");
    SynchroSample<int, SynchroSampleInfoExt> bsWrite; // you can omit the SynchroSampleInfoExt if you just want to use normal sample headers
    int intArray[] = {1,2,3};
    bsWrite.SetDataPointer(intArray, 3);
    myBuffer.Push(bsWrite);

    Synchrony<int, SynchroSampleInfoExt> yourBuffer;
    yourBuffer.Open("Synchrony_Buffer");
    SynchroSample<int, SynchroSampleInfoExt> bsRead = myBuffer.ReadNewest();
    printf("Buffer contents: %d%d%d\n", bsRead.GetData(0), bsRead.GetData(1), bsRead.GetData(2));

	return 0;
}

